package com.example.managemyself;

import android.app.Application;
import android.content.Context;
import android.util.Log;

import com.example.managemyself.config.AppConfig;
import com.example.managemyself.config.DatabaseInitializer;
import com.example.managemyself.data.database.AppDatabase;
import com.example.managemyself.util.DatabaseRepairHelper;
import com.example.managemyself.util.DatabaseSettingsManager;
import com.example.managemyself.util.MySQLConnectionHelper;
import com.example.managemyself.util.NotificationHelper;
import com.example.managemyself.util.SettingsManager;
import com.example.managemyself.util.ThemeHelper;
import com.example.managemyself.util.UserManager;
import com.example.managemyself.util.DeepSeekHelper;

/**
 * 自定义Application类，用于初始化全局组件
 * 
 * 初始化顺序：
 * 1. 配置管理器 - 提供基础配置
 * 2. 用户管理器 - 管理用户状态
 * 3. 数据库连接 - 建立数据库连接
 * 4. 数据库初始化 - 创建表结构和默认数据
 * 5. 本地数据库 - Room数据库
 * 6. 设置管理器 - 应用设置
 * 7. 主题应用 - UI主题
 * 8. 通知系统 - 通知渠道
 * 
 * @author ManageMyself Team
 * @version 2.0
 */
public class ManageMyself extends Application {
    
    private static final String TAG = "ManageMyself";
    private static Context appContext;
    private static boolean isInitialized = false;
    
    @Override
    public void onCreate() {
        super.onCreate();
        
        long startTime = System.currentTimeMillis();
        Log.i(TAG, "Application initialization started");
        
        // 设置全局异常处理器
        setupGlobalExceptionHandler();
        
        try {
            appContext = getApplicationContext();
            initializeComponents();
            isInitialized = true;
            
            long endTime = System.currentTimeMillis();
            Log.i(TAG, "Application initialization completed in " + (endTime - startTime) + "ms");
            
        } catch (Exception e) {
            Log.e(TAG, "Critical error during application initialization", e);
            // 在初始化失败时，仍然设置基本的上下文
            appContext = getApplicationContext();
        }
    }
    
    /**
     * 设置全局异常处理器
     */
    private void setupGlobalExceptionHandler() {
        Thread.setDefaultUncaughtExceptionHandler((thread, throwable) -> {
            Log.e(TAG, "未捕获的异常", throwable);
            
            // 检查是否是数据库相关错误
            if (isDatabaseError(throwable)) {
                Log.w(TAG, "检测到数据库错误，尝试修复");
                try {
                    DatabaseRepairHelper.repairDatabaseMigrationError(this);
                    Log.i(TAG, "数据库错误修复完成");
                } catch (Exception e) {
                    Log.e(TAG, "数据库修复失败", e);
                }
            }
            
            // 调用系统默认处理器
            System.exit(1);
        });
    }
    
    /**
     * 判断是否为数据库相关错误
     */
    private boolean isDatabaseError(Throwable throwable) {
        String message = throwable.getMessage();
        if (message == null) return false;
        
        return message.contains("duplicate column") ||
               message.contains("SQLiteException") ||
               message.contains("database") ||
               message.contains("migration") ||
               message.contains("Room") ||
               message.contains("SQLITE_ERROR");
    }
    
    /**
     * 按顺序初始化所有组件
     */
    private void initializeComponents() {
        // 第一阶段：核心配置初始化
        initializeCoreConfig();
        
        // 第二阶段：用户和数据库初始化
        initializeDatabaseAndUser();
        
        // 第三阶段：应用功能初始化
        initializeAppFeatures();
        
        // 第四阶段：UI和通知初始化
        initializeUIAndNotifications();
        
        // 调试信息输出
        if (AppConfig.getInstance().isDebugMode()) {
            printInitializationInfo();
        }
    }
    
    /**
     * 第一阶段：初始化核心配置
     */
    private void initializeCoreConfig() {
        try {
            Log.d(TAG, "Phase 1: Initializing core configuration");
            
            // 1. 初始化配置管理器（最先初始化）
            AppConfig.getInstance().init(this);
            Log.d(TAG, "✓ AppConfig initialized");
            
        } catch (Exception e) {
            Log.e(TAG, "Error in core config initialization", e);
            throw new RuntimeException("Failed to initialize core configuration", e);
        }
    }
    
    /**
     * 第二阶段：初始化数据库和用户管理
     */
    private void initializeDatabaseAndUser() {
        try {
            Log.d(TAG, "Phase 2: Initializing database and user management");
            
            // 2. 初始化用户管理器
            UserManager.getInstance().init(this);
            Log.d(TAG, "✓ UserManager initialized");
            
            // 3. 初始化数据库连接（允许失败）
            try {
                MySQLConnectionHelper.getInstance().initialize(this);
                Log.d(TAG, "✓ MySQL connection helper initialized");
                
                // 4. 初始化数据库结构和默认数据
                DatabaseInitializer.getInstance().initializeDatabase(this);
                Log.d(TAG, "✓ Database structure initialized");
            } catch (Exception e) {
                Log.w(TAG, "MySQL initialization failed, continuing with local database only", e);
            }
            
            // 5. 初始化本地数据库（带修复功能）
            initializeLocalDatabase();
            Log.d(TAG, "✓ Local Room database initialized");
            
        } catch (Exception e) {
            Log.e(TAG, "Error in database and user initialization", e);
            // 数据库初始化失败不应该阻止应用启动，记录错误并继续
        }
    }
    
    /**
     * 第三阶段：初始化应用功能
     */
    private void initializeAppFeatures() {
        try {
            Log.d(TAG, "Phase 3: Initializing application features");
            
            // 6. 初始化设置管理器
            SettingsManager.getInstance();
            Log.d(TAG, "✓ SettingsManager initialized");
            
            // 7. 初始化数据库设置管理器
            DatabaseSettingsManager.getInstance();
            Log.d(TAG, "✓ DatabaseSettingsManager initialized");
            
            // 8. 初始化DeepSeek助手
            DeepSeekHelper.initialize(this);
            Log.d(TAG, "✓ DeepSeekHelper initialized");
            
        } catch (Exception e) {
            Log.e(TAG, "Error in app features initialization", e);
            // 功能初始化失败不应该阻止应用启动
        }
    }
    
    /**
     * 第四阶段：初始化UI和通知
     */
    private void initializeUIAndNotifications() {
        try {
            Log.d(TAG, "Phase 4: Initializing UI and notifications");
            
            // 9. 应用主题
            String theme = SettingsManager.getInstance().getCurrentTheme(this);
            ThemeHelper.applyTheme(theme);
            Log.d(TAG, "✓ Theme applied: " + theme);
            
            // 10. 创建通知渠道
            NotificationHelper.createNotificationChannels(this);
            Log.d(TAG, "✓ Notification channels created");
            
        } catch (Exception e) {
            Log.e(TAG, "Error in UI and notifications initialization", e);
            // UI初始化失败不应该阻止应用启动
        }
    }
    
    /**
     * 打印初始化信息
     */
    private void printInitializationInfo() {
        try {
            Log.d(TAG, "=== Application Configuration ===");
            AppConfig.getInstance().printAllConfigs();
            
            Log.d(TAG, "=== User Management Status ===");
            UserManager userManager = UserManager.getInstance();
            Log.d(TAG, "Local mode: " + userManager.isLocalMode());
            Log.d(TAG, "User logged in: " + userManager.isLoggedIn());
            if (userManager.isLoggedIn()) {
                Log.d(TAG, "Current user: " + userManager.getCurrentUser().getUsername());
            }
            
        } catch (Exception e) {
            Log.w(TAG, "Error printing initialization info", e);
        }
    }
    
    /**
     * 获取应用程序上下文
     */
    public static Context getAppContext() {
        return appContext;
    }
    
    /**
     * 检查应用是否已完全初始化
     */
    public static boolean isInitialized() {
        return isInitialized;
    }
    
    /**
     * 获取应用版本信息
     */
    public static String getAppVersion() {
        if (appContext != null) {
            try {
                return appContext.getPackageManager()
                        .getPackageInfo(appContext.getPackageName(), 0)
                        .versionName;
            } catch (Exception e) {
                Log.w(TAG, "Error getting app version", e);
            }
        }
        return "Unknown";
    }
    
    @Override
    public void onTerminate() {
        super.onTerminate();
        Log.i(TAG, "Application terminating");
        
        // 清理资源
        try {
            UserManager.cleanup();
            Log.d(TAG, "Resources cleaned up");
        } catch (Exception e) {
            Log.w(TAG, "Error during cleanup", e);
        }
    }
    
    @Override
    public void onLowMemory() {
        super.onLowMemory();
        Log.w(TAG, "Low memory warning received");
        
        // 可以在这里实现内存清理逻辑
        System.gc();
    }
    
    /**
     * 初始化本地数据库，包含自动修复功能
     */
    private void initializeLocalDatabase() {
        try {
            // 尝试正常初始化数据库
            AppDatabase.getInstance(this);
            Log.d(TAG, "数据库正常初始化成功");
            
        } catch (Exception e) {
            Log.w(TAG, "数据库初始化失败，尝试自动修复: " + e.getMessage());
            
            // 检查是否是迁移错误
            if (isDatabaseError(e)) {
                Log.w(TAG, "检测到数据库迁移错误，使用专门的修复方法");
                try {
                    // 使用专门的迁移错误修复
                    DatabaseRepairHelper.repairDatabaseMigrationError(this);
                    Log.i(TAG, "数据库迁移错误修复成功");
                    
                    // 重新尝试初始化
                    AppDatabase.getInstance(this);
                    Log.d(TAG, "修复后数据库初始化成功");
                    return;
                } catch (Exception migrationFixError) {
                    Log.e(TAG, "迁移错误修复失败，尝试一般修复", migrationFixError);
                }
            }
            
            // 使用一般修复工具尝试修复数据库
            DatabaseRepairHelper repairHelper = new DatabaseRepairHelper(this);
            boolean repaired = repairHelper.checkAndRepairDatabase();
            
            if (repaired) {
                Log.i(TAG, "数据库一般修复成功");
                try {
                    // 重新尝试初始化
                    AppDatabase.getInstance(this);
                    Log.d(TAG, "修复后数据库初始化成功");
                } catch (Exception retryException) {
                    Log.e(TAG, "修复后仍然无法初始化数据库", retryException);
                    // 最后尝试强制重建
                    forceRebuildDatabase();
                }
            } else {
                Log.e(TAG, "数据库修复失败，尝试强制重建");
                forceRebuildDatabase();
            }
        }
    }
    
    /**
     * 强制重建数据库
     */
    private void forceRebuildDatabase() {
        try {
            Log.w(TAG, "开始强制重建数据库...");
            boolean rebuilt = DatabaseRepairHelper.forceRebuildDatabase(this);
            if (rebuilt) {
                Log.i(TAG, "数据库强制重建成功");
            } else {
                Log.e(TAG, "数据库强制重建失败");
                throw new RuntimeException("数据库初始化完全失败");
            }
        } catch (Exception e) {
            Log.e(TAG, "强制重建数据库时发生错误", e);
            throw new RuntimeException("数据库初始化和修复都失败", e);
        }
    }
} 